package com.example.g5project.customer.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.example.g5project.customer.mapper.CustomerMapper;
import com.example.g5project.customer.model.dto.CustomerDTO;
import com.example.g5project.customer.model.param.CustomerEditParam;
import com.example.g5project.customer.model.param.CustomerLoginParam;
import com.example.g5project.customer.model.param.CustomerRegisterParam;
import com.example.g5project.customer.model.po.BasePO;
import com.example.g5project.customer.model.po.CustomerPO;
import com.example.g5project.customer.service.CustomerService;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.stereotype.Service;

@Slf4j
@Service
public class CustomerServiceImpl extends ServiceImpl<CustomerMapper, CustomerPO> implements CustomerService {

    @Override
    public Integer register(CustomerRegisterParam registerParam) {
        int count = new LambdaQueryChainWrapper<>(this.baseMapper)
            .eq(CustomerPO::getPhone, registerParam.getPhone())
            .count();
        if (count != 0) {
            throw new IllegalArgumentException("账号已存在");
        }

        CustomerPO po = CustomerPO.builder()
            .name(registerParam.getName())
            .password(registerParam.getPassword())
            .phone(registerParam.getPhone())
            .contactName(registerParam.getContactName())
            .contactPhone(registerParam.getContactPhone())
            .build();
        this.save(po);
        return po.getId();
    }

    @Override
    public boolean edit(CustomerEditParam editParam) {
        CustomerPO po = CustomerPO.builder()
            .name(editParam.getName())
            .password(editParam.getPassword())
            .phone(editParam.getPhone())
            .contactName(editParam.getContactName())
            .contactPhone(editParam.getContactPhone())
            .build();
        return new LambdaUpdateChainWrapper<>(this.baseMapper)
            .eq(BasePO::getId, editParam.getCustomerId())
            .update(po);
    }

    @Override
    public CustomerDTO login(CustomerLoginParam loginParam) {
        LambdaQueryWrapper<CustomerPO> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.eq(CustomerPO::getPhone, loginParam.getPhone());
        Integer count = this.baseMapper.selectCount(queryWrapper);
        if (count == 0) {
            return null;
        }
        if (count > 1) {
            log.error("DB中存在多条相同手机号的账号，phone = {}", loginParam.getPhone());
        }
        queryWrapper.eq(CustomerPO::getPassword, loginParam.getPassword());
        List<CustomerPO> pos = this.baseMapper.selectList(queryWrapper);
        return CollectionUtils.isEmpty(pos) ? null : pos.get(0).convert2DTO();
    }

    @Override
    public CustomerDTO detailById(Integer id) {
        CustomerPO po = this.getById(id);
        return po.convert2DTO();
    }

    @Override
    public List<CustomerDTO> detailByIds(Collection<Integer> ids) {
        if (CollectionUtils.isEmpty(ids) || Collections.min(ids) <= 0) {
            return Collections.emptyList();
        }
        List<CustomerPO> pos = new LambdaQueryChainWrapper<>(this.baseMapper)
            .in(BasePO::getId, ids)
            .list();
        return pos.stream().map(CustomerPO::convert2DTO).collect(Collectors.toList());
    }

    @Override
    public boolean allExist(Collection<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return true;
        }
        Integer count = new LambdaQueryChainWrapper<>(this.baseMapper)
            .in(BasePO::getId, ids)
            .count();
        return count == CollectionUtils.size(ids);
    }
}
